/**
 * @(#)ChannelMonitorNewUsersImpl.java 2017年1月12日
 * Copyright(C) 2015 ZHEXIN IT CO.,LTD. All rights reserved.
 */
package org.jsbd.boss.service.impl;

import java.text.DecimalFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;

import org.apache.commons.lang.StringUtils;
import org.jsbd.boss.common.ExportExcel;
import org.jsbd.boss.dao.IApkSimulatorDAO;
import org.jsbd.boss.dao.IChannelApkInfoDAO;
import org.jsbd.boss.dao.IDmChannelRetentDAO;
import org.jsbd.boss.dao.IEmailInfoDAO;
import org.jsbd.boss.domian.ChannelApkConfigTimeModel;
import org.jsbd.boss.domian.ChannelApkInfo;
import org.jsbd.boss.domian.ChannelMonitorExportInfo;
import org.jsbd.boss.domian.EmailInfo;
import org.jsbd.boss.domian.channel.ChannelApkConfig;
import org.jsbd.boss.service.IApkTaskQueryService;
import org.jsbd.boss.service.IChannelApkInfoService;
import org.jsbd.boss.service.IChannelLimitService;
import org.jsbd.boss.service.IChannelMonitorNewUsers;
import org.jsbd.boss.util.DateUtil;
import org.jsbd.boss.util.EmailSslUtils;
import org.jsbd.boss.util.PropertiesUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import edu.hziee.cap.common.util.EmailUtil;

/**
 * TODO 请加入本类的说明
 * 
 * @author <a href="mailto:zhangbinghua@zhexinit.com" >zbh</a>
 * @version 1.0.0
 */
@Service
public class ChannelMonitorNewUsersImpl implements IChannelMonitorNewUsers {
	public static final Logger LOGGER = LoggerFactory.getLogger(ChannelMonitorNewUsersImpl.class);

	private String dailyReportPath = PropertiesUtil.getValue("dailyReportPath", "/tmp/report/");
	private EmailSslUtils emailUtil;
	private String env = "WARNING";
	private String[] sendTo = {};
	private static String DATE_PATTERN = "yyyy-MM-dd";

	@Autowired
	private IDmChannelRetentDAO dmChannelRetentDAO;
    @Autowired
    private IChannelApkInfoDAO channelApkInfoDAO;
    @Autowired
    private IEmailInfoDAO emailInfoDAO;
	@Autowired
	private IChannelApkInfoService channelApkInfoService;
	@Autowired
	private IChannelLimitService channelLimitService;
	@Autowired
	private IChannelApkInfoService channelApkService;
	@Resource
	private IApkTaskQueryService apkTaskQueryService;
	@Resource
	private IApkSimulatorDAO apkSimulatorDAO;
	
	
	private final long ALERTTIME = 30*60*1000;//半小时的毫秒数
	@Override
	public void reportNewUsers() {
		try {
			List<String> emails=new ArrayList<String>();
			List<EmailInfo> emaillist = emailInfoDAO.getAllEmailInfo();
			if (emaillist == null || emaillist.size() == 0) {
				return;
			}
			for (int i = 0; i < emaillist.size(); i++) {
				EmailInfo email = emaillist.get(i);
				emails.add(email.getEmail());
				
			}
			sendTo = emails.toArray(new String[0]);
			Calendar calendar = Calendar.getInstance();
			String time = new SimpleDateFormat(DateUtil.DATE_PATTEN_YY_MM_DD_HHMMSS).format(calendar.getTime());
			String date = DateUtil.getCurrentDateStr();
			String yesterday = DateUtil.getPreviousDateStr();
			//今天所有新增用户
			List<ChannelMonitorExportInfo> totolNewUsers = null;// dmChannelRetentDAO.getChannelNewUserExportInfo(date, yesterday);
			//前十分钟新增用户
			List<ChannelMonitorExportInfo> moniterNewUsers = dmChannelRetentDAO.getChannelMonitorExportInfo(time, date, yesterday);
			String attachment = dailyReportPath + "CHANNEL_NEWUSER_RATE_" + DateUtil.getCurrentDateTime() + ".xls";
			// 新增的总量header
			String[] channeltotaladdHeaders = { "mark", "apk名称", "渠道名称", "有手机号码数量", "新增总数", "手机号码获取率", "最后执行时间", "昨日有号码数量", "昨日总数", "昨日获取率" };
			// 10分钟内新增量header
			String[] channeladdHeaders = { "mark", "apk名称", "渠道名称", "有手机号码数量", "新增总数", "手机号码获取率", "最后执行时间", "昨日有号码数量", "昨日总数", "昨日获取率" };
			
			// 半小时未做的业务做警报
			String content = buildEmailContent(totolNewUsers, moniterNewUsers);
			
			ExportExcel excel = new ExportExcel();
			if (totolNewUsers != null) {
				int index = 0;
				excel.exportMultiSheetExcel2003(index++, "当天新增的总量", channeltotaladdHeaders, totolNewUsers, attachment, DATE_PATTERN);
				excel.exportMultiSheetExcel2003(index++, "10分钟内新增量", channeladdHeaders, moniterNewUsers,attachment, DATE_PATTERN);
			}
			
			
			emailUtil.setTo(sendTo);
			emailUtil.setSubject(env + "_" + DateUtil.getCurrentDateTime() + "_网盟新增用户统计数据");
			emailUtil.setContent(content);
			emailUtil.setAttchmentFileList(new String[] { attachment });
			emailUtil.send();
		} catch (Exception e) {
			LOGGER.error("Any error msg that u want to write", e);
		}
		LOGGER.info("Send email over ...");

	}

	public EmailSslUtils getEmailUtil() {
		return emailUtil;
	}

	public void setEmailUtil(EmailSslUtils emailUtil) {
		this.emailUtil = emailUtil;
	}

	/**
	 * 
	 * buildEmailContent:组织邮件内容
	 * @author <a href="mailto:zhangbinghua@zhexinit.com" >zbh</a>
	 * @param totolNewUsers
	 * @param moniterNewUsers
	 * @return
	 */
	private String buildEmailContent(List<ChannelMonitorExportInfo> totolNewUsers ,List<ChannelMonitorExportInfo> moniterNewUsers ){
		String content = getTotalSimulatorNum();
		content =content+ "<table border=\"0\" cellpadding=\"1\" cellspacing=\"0\" nowrap=\"true\" style=\"border-collapse:collapse;table-layout:fixed\" width=\"1056\">	<tbody><tr height=\"17\" style=\"mso-height-source:userset;12.75pt\">"
				+ "<td align=\"center\" class=\"style1\" style=\"border-left:none\">apk名称</td>"
				+ "<td align=\"center\" class=\"style2\" style=\"border-left:none\">预设总量</td>"
				+ "<td align=\"center\" class=\"style2\" style=\"border-left:none\">新增总数</td>"
				+ "<td align=\"center\" class=\"style2\" style=\"border-left:none\">最后执行时间</td>"
				+ "<td align=\"center\" class=\"style2\" style=\"border-left:none\">昨日同时段总量</td>"
				+ "<td align=\"center\" class=\"style2\" style=\"border-left:none\">执行量/预设量比例</td>"
				+ "<td align=\"center\" class=\"style2\" style=\"border-left:none\">前10分钟总量</td>"
				+ "<td align=\"center\" class=\"style2\" style=\"border-left:none\">昨日同时段10分钟总量</td>";
		
		for(ChannelMonitorExportInfo channelMonitorExportInfo : moniterNewUsers){
			String mark = channelMonitorExportInfo.getMark();
			//因为不能跨库查询，需要先获取渠道包的信息
			ChannelApkConfig  t = channelApkInfoService.selectChannelApkConfig(mark);
			if (t != null && t.getApkName()!=null) {
				channelMonitorExportInfo.setApkName(t.getApkName());
				channelMonitorExportInfo.setChannelName(t.getChannelName());
			}else{
				//兼容老的配置表
				ChannelApkInfo  channelApkInfo =  channelApkInfoDAO.getConfigByMarkForPage(mark);
				if (channelApkInfo != null) {
					channelMonitorExportInfo.setApkName(channelApkInfo.getApkName());
					channelMonitorExportInfo.setChannelName(channelApkInfo.getChannelName());
				}
			}
		}
		
		for(ChannelMonitorExportInfo channelMonitorExportInfo : totolNewUsers){
			String mark = channelMonitorExportInfo.getMark();
			//因为不能跨库查询，需要先获取渠道包的信息
			ChannelApkConfig  t = channelApkInfoService.selectChannelApkConfig(mark);
			if (t != null && t.getApkName()!=null) {
				channelMonitorExportInfo.setApkName(t.getApkName());
				channelMonitorExportInfo.setChannelName(t.getChannelName());
				channelMonitorExportInfo.setDaylimit(t.getDaylimit());
			}else{
				//兼容老的配置表
				ChannelApkInfo  channelApkInfo = channelApkInfoDAO.getConfigByMarkForPage(mark);
				if (channelApkInfo != null) {
					channelMonitorExportInfo.setApkName(channelApkInfo.getApkName());
					channelMonitorExportInfo.setChannelName(channelApkInfo.getChannelName());
					channelMonitorExportInfo.setDaylimit(channelApkInfo.getDaylimit());
				}else{
					LOGGER.error("[{}] is null",mark);
					continue;
				}
			}
			/*判断是否需要报警
			 * 按最后执行时间判断，超过半小时就报警
			 */
			String lastexetime = channelMonitorExportInfo.getLastexetime();
			//计算当前时间预计执行的数据
			int planNum = 0;
			int total = 0;
			try{
				total = Integer.parseInt(channelMonitorExportInfo.getTotal());
			}catch(Exception e){
				
			}
			if (channelMonitorExportInfo.getDaylimit() > 0) {
				planNum = getPlanNum(channelMonitorExportInfo.getDaylimit(), mark);
			}
			if (isalerm(lastexetime)) {
				content += "<tr height=\"17\" style=\"background-color:red;mso-height-source:userset;12.75pt\">";
			} else {
				content += "<tr height=\"17\" style=\"mso-height-source:userset;12.75pt\">";
			}
			   

			String ratio = "";
			if (planNum > 0) {
				ratio = new DecimalFormat("######0.00").format( (double)total/ planNum);
			}
			 
			content+= "<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+channelMonitorExportInfo.getApkName()+"</td>";
			content+= "<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+channelMonitorExportInfo.getDaylimit()+"|"+planNum+"</td>";
			content+= "<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+total+"</td>";
			content+= "<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+lastexetime+"</td>";
			content+= "<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+channelMonitorExportInfo.getYesterdayTotal()+"</td>";
			content+= "<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+ratio+"</td>";

			//查询mark分时的执行量
			for(ChannelMonitorExportInfo m : moniterNewUsers){
				if(mark.equals(m.getMark())){
					String fstotal="0";
					if(m.getTotal()!=null){
						fstotal = m.getTotal();
					}
					String yesterdayfstotal="0";
					if(m.getYesterdayTotal()!=null){
						yesterdayfstotal =m.getYesterdayTotal();
					}
					content+="<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+fstotal+"</td>";
					content+="<td align=\"center\" class=\"style3\" style=\"border-top:none;border-left:none\">"+yesterdayfstotal+"</td>";
				}
			}
				  
			
		}
		 content +=  "</tbody></table>";
		return content;
	}
	
	private int getPlanNum(int daylimit,String mark){
		ChannelApkConfigTimeModel model = channelLimitService.getCurrentAddLimitModel(mark,daylimit);
		if (model != null) {
			return model.getSpDayLimit();//(int) (daylimit * (model.getTimePercent() / 100));
		} else {
			return daylimit;
		}
	}
	/*
	 * 判断是否需要报警 按最后执行时间判断，超过半小时就报警
	 */
	private boolean isalerm(String lastexetime) {
		if (StringUtils.isBlank(lastexetime)) {
			return true;
		}
		try {
			Date date = new SimpleDateFormat(DateUtil.DATE_PATTEN_YY_MM_DD_HHMMSS).parse(lastexetime);
			Date a = new Date();
			long sec = a.getTime() - date.getTime();
			if (sec > ALERTTIME) {
				return true;
			} else {
				return false;
			}
		} catch (ParseException e) {
			LOGGER.error("时间转换异常", e);
			return true;
		}

	}
	
	/*
	 * 判断是否需要报警 按最后已经执行的数量和计划执行的数量，小于百分之80就报警
	 */
	private boolean isPlanNumAlerm(int total, int planNum) {
		if (planNum <= 0) {
			return true;
		}
		try {
			double ratio = (double)total / planNum;
			if (ratio <= 0.8) {
				return true;
			} else {
				return false;
			}
		} catch (Exception e) {
			LOGGER.error("isPlanNumAlerm异常", e);
			return true;
		}
	}

	/**
	 * 
	 * getTotalSimulter:获取模拟器信息
	 * @author <a href="mailto:zhangbinghua@zhexinit.com" >zbh</a>
	 * @return
	 */
	private String getTotalSimulatorNum(){
		List<ChannelApkConfig> list = apkSimulatorDAO.getApkInfoList(null);
		list = apkTaskQueryService.queryApkConfigList(list);
		Map<String,Integer> result = new HashMap<String,Integer>();
		for(ChannelApkConfig channelApkConfig : list){
			String sysVer = channelApkConfig.getSysVer();
			Integer curr = 0;
			String needNums=channelApkConfig.getNeedSimulators();
			if(StringUtils.isNotBlank(needNums)){
				curr = Integer.parseInt(needNums);
			}
			Integer total = result.get(sysVer);
			if (total == null) {
				total = 0;
			}
			result.put(sysVer, total + curr);
		}
		String content="";
		for(Map.Entry<String,Integer> entry:result.entrySet()){
			content+="版本号："+entry.getKey()+"|";
			content+="需要模拟器数量："+entry.getValue();
		}
		LOGGER.info("-----------------------------------------");
		LOGGER.info("getTotalSimulatorNum:"+content);
		return content;
		
	}
}
